import javax.xml.namespace.QName;

/**
 * @author xhw
 */

//1.继承：父类
class Animal {

    private String name;

    // 基类构造函数，用于初始化字段
    public Animal(String name) {
        this.name = name;
    }


    public Animal() {

    }

    //去掉private报错  为什么
    //这是因为设置了private，子类无法访问到父类的字段，所以没有办法被子类重写，假如去掉的话就是默认的default，是允许包内访问的
    public void eat() {
        System.out.println("Animal eat");
    }


}

//2.继承：子类
class Dog extends Animal {

    //子类的构造函数调用了父类的构造函数
    public Dog(String name) {
        super(name);
    }

    public Dog() {
        super();
    }

    //重写的方法
    @Override
    public void eat() {
        System.out.println("Dog eat");
    }

}

//定义一个接口
interface Runner {
    //接口中的抽象方法
    void run();
}

//接口的实现，有dog嘞继承了Animal类，所以这里用implements
class Dog2 extends Animal implements Runner {

    public Dog2(String name) {
        super(name);
    }

    //实现的接口方法
    @Override
    public void run() {
        System.out.println("Dog run");
    }
}


/**
 * 1.继承
 * 2.接口
 * 3.重写
 * 4.重载
 * 5.构造函数（有继承的时候，相关知识点总结出来，包括字段初始化）
 * 构造函数不能是抽象的abstract 、static或final。
 * <p>
 * 1.构造函数可以重载，但不能被重写。
 * 2.构造函数可以分为3种类型：
 * 无参数构造函数
 * 默认构造函数
 * 参数构造函数
 */

public class 封装继承重载抽象多态 {
    //重载
    //函数名+参数列表 = 函数签名

    public static void main(String[] args) {
        封装继承重载抽象多态 overLoad = new 封装继承重载抽象多态();
        String s = "这是一个字符串";
        Object o = "这是一个对象";

        //显式类型转换为Object类型，调用fun2(Object obj)
        overLoad.fun1((Object) s);

        //调用fun1(String str)
        overLoad.fun1("hello");

        //调用fun2(Object str)
        overLoad.fun1("hello");

        //调用fun3(Object... str)
        overLoad.fun1("hello", "world");

        Animal animal = new Animal();
        Dog dog = new Dog();
        //调用test1(Animal animal)
        overLoad.test1(animal);
        overLoad.test1(dog);

        //调用test2(Object obj)
        overLoad.test2(o);
        overLoad.test2(s);

    }

    //重载方法1
    public void fun1(String str) {
        System.out.println("call fun1(String str)");
    }

    //重载方法2:Object是所有类的父类
    public void fun1(Object str) {
        System.out.println("call fun1(Object str)");
    }

    //重载方法3:可变参数
    public void fun1(Object... str) {
        System.out.println("call fun1(Object... str)");
    }

    public void test1(Animal animal) {
        System.out.println("Animal");
    }

    public void test1(Dog dog) {
        System.out.println("Dog");
    }

    public void test2(Object obj) {
        System.out.println("Object");
    }

    public void test2(String str) {
        System.out.println("String");
    }
}
